package com.aliyun.heiyu.powermaster.server.rotary.service.impl;

import com.alibaba.fastjson.JSON;
import com.aliyun.heiyu.powermaster.proto.CabinetsAndServerReply;
import com.aliyun.heiyu.powermaster.proto.CabinetsAndServerTemp;
import com.aliyun.heiyu.powermaster.proto.CabinetsAndServerTempReply;
import com.aliyun.heiyu.powermaster.proto.RecommendCabinetReply;
import com.aliyun.heiyu.powermaster.server.Error;
import com.aliyun.heiyu.powermaster.server.manager.DeviceManager;
import com.aliyun.heiyu.powermaster.server.manager.DeviceManagerImpl;
import com.aliyun.heiyu.powermaster.server.rotary.contants.CommonUrlContant;
import com.aliyun.heiyu.powermaster.server.rotary.dao.ServerDAO;
import com.aliyun.heiyu.powermaster.server.rotary.dao.impl.ServerDAOImpl;
import com.aliyun.heiyu.powermaster.server.rotary.object.dto.CabinetDTO;
import com.aliyun.heiyu.powermaster.server.rotary.object.entity.DeviceCommonEntity;
import com.aliyun.heiyu.powermaster.server.rotary.object.entity.ServerCollectInfoEntity;
import com.aliyun.heiyu.powermaster.server.rotary.object.thread.ServerDataThread;
import com.aliyun.heiyu.powermaster.server.rotary.service.ServerService;
import com.aliyun.heiyu.powermaster.server.rotary.utils.HttpUtil;
import com.aliyun.heiyu.powermaster.server.rotary.utils.ThreadPoolUtil;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.json.JSONObject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.math.BigDecimal;
import java.util.Calendar;
import java.util.List;
import java.util.Map;

/**
 * @Description 服务器业务实现类
 * @Author shun.zhang
 * @Date 2019/12/31 11:21
 **/
public class ServerServiceImpl implements ServerService {
    private static int count = 90;
    private static Logger logger = LoggerFactory.getLogger(ServerServiceImpl.class);

    private static List<DeviceCommonEntity> serverList = null;
    private ServerDAO serverDAO;
   private DeviceManager deviceManager = DeviceManagerImpl.getInstance();

    public ServerServiceImpl() {
        serverDAO = new ServerDAOImpl();
    }

    public ServerServiceImpl(int key) {
        serverDAO = new ServerDAOImpl();
    }

    @Override
    public int saveServerData() {
        logger.info("保存服务器数据");
        //1.获取所有的服务器（存缓存）
        if (CollectionUtils.isEmpty(serverList)) {
            serverList = serverDAO.getServerList();
        }
        if (CollectionUtils.isEmpty(serverList)) {
            return 0;
        }
        serverList.forEach(server -> {
            //2.构造假数据
            String randomNum = System.currentTimeMillis()+ "";
            int num = Integer.valueOf(randomNum.substring(randomNum.length()-1));
            ServerCollectInfoEntity info = new ServerCollectInfoEntity();
            info.setCollect_time(Calendar.getInstance().getTime());
            info.setGmt_create(Calendar.getInstance().getTime());
            info.setInlet_temp(new BigDecimal(28 + num));
            info.setServer_sn(server.getDevice_id());
            //3.保存假数据
            ThreadPoolUtil.execute(new ServerDataThread(serverDAO, info));
        });
        return serverList.size();
    }

    /**
     * @return List<CabinetDTO>
     * @Description 获取系统中机柜及其温度最高服务器
     **/
    @Override
    public CabinetsAndServerTempReply queryCabinetServerTemp() {
        CabinetsAndServerTempReply.Builder cabinetsReply = CabinetsAndServerTempReply.newBuilder();
        CabinetsAndServerTempReply.Data.Builder cabinetsList = CabinetsAndServerTempReply.Data.newBuilder();
        List<CabinetDTO> cabinetsAndServerTemp = serverDAO.getCabinetsAndServerTemp();
        if(CollectionUtils.isEmpty(cabinetsAndServerTemp)){
            cabinetsReply.setErrCode(Error.SUCCESS.getCode()).setErrMsg(Error.SUCCESS.getMessage());
            return cabinetsReply.build();
        }
        for(CabinetDTO cabinetDTO:cabinetsAndServerTemp){
            CabinetsAndServerTemp.Builder builder = CabinetsAndServerTemp.newBuilder();
            if(cabinetDTO.getInlet_temp()==null ||cabinetDTO.getInlet_temp().equals("") ){
                builder.setInletTemp(0);
            }else{
                builder.setInletTemp(cabinetDTO.getInlet_temp().doubleValue());
            }
            if(StringUtils.isNotBlank(cabinetDTO.getServer_sn())){
                builder.setServerSn(cabinetDTO.getServer_sn());
            }else{
                builder.setServerSn("");
            }
            if(StringUtils.isNotBlank(cabinetDTO.getLocated_cabinet())){
                builder.setLocatedCabinet(cabinetDTO.getLocated_cabinet());
            }else{
                builder.setLocatedCabinet("");
            }
            cabinetsList.addCabinets(builder.build());
        }
        cabinetsReply.setData(cabinetsList);
        cabinetsReply.setErrCode(0);
        cabinetsReply.setErrMsg("ok");
        return cabinetsReply.build();
    }

    @Override
    public CabinetsAndServerTempReply queryMicrothermCabinetServerTemp(){
        CabinetsAndServerTempReply.Builder cabinetsReply = CabinetsAndServerTempReply.newBuilder();
        CabinetsAndServerTempReply.Data.Builder cabinetsList = CabinetsAndServerTempReply.Data.newBuilder();
        List<CabinetDTO> cabinetsAndServerTemp = serverDAO.queryMicrothermCabinetServerTemp();
        if(CollectionUtils.isEmpty(cabinetsAndServerTemp)){
            cabinetsReply.setErrCode(500).setErrMsg("数据为空");
            return cabinetsReply.build();
        }
        for(CabinetDTO cabinetDTO:cabinetsAndServerTemp){
            CabinetsAndServerTemp.Builder builder = CabinetsAndServerTemp.newBuilder();
            builder.setInletTemp(cabinetDTO.getInlet_temp().doubleValue());
            builder.setServerSn(cabinetDTO.getServer_sn());
            builder.setLocatedCabinet(cabinetDTO.getLocated_cabinet());
            cabinetsList.addCabinets(builder.build());
        }
        cabinetsReply.setData(cabinetsList);
        cabinetsReply.setErrCode(0);
        cabinetsReply.setErrMsg("ok");
        return cabinetsReply.build();
    }

    @Override
    public CabinetsAndServerReply getCabinetTempByDeviceId(String device_id) {
        CabinetsAndServerReply.Builder reply = CabinetsAndServerReply.newBuilder();
        CabinetsAndServerReply.Data data = serverDAO.getCabinetTempByDeviceId(device_id);
        reply.setData(data);
        reply.setErrCode(0);
        reply.setErrMsg("ok");
        return reply.build();
    }

    @Override
    public RecommendCabinetReply recommendCabinet() {
        RecommendCabinetReply.Builder builder = RecommendCabinetReply.newBuilder();
        CabinetsAndServerTempReply reply = queryMicrothermCabinetServerTemp();
        CabinetsAndServerTemp cabinets = reply.getData().getCabinets(0);
        builder.setCabinet(cabinets);
        builder.setErrCode(0);
        builder.setErrMsg("ok");
        return builder.build();
    }

    @Override
    public Map<String,Integer> getServerTemps(String[] sns) {
        StringBuilder request = new StringBuilder();
        request.append("{\"place\":\"huzhou\", \"sns\":[");
        request.append("\"819257313\",\"819257339\",\"819257298\",\"819257312\",\"819257301\",\"7CE920P04G\",\"7CE920P044\",\"7CE920P01L\",\"819257340\",\"819257399\",\"819257310\",\"219251615\",\"219251614\",\"219251616\",\"819257360\"")
            .append("]}");
        logger.info("请求："+request.toString());
        JSONObject jsonObject = HttpUtil.postRequest(request.toString(), CommonUrlContant.OVER_HEAT_PREDICT);
        if (null != jsonObject) {
            String data = jsonObject.get("data").toString();
            Map<String, Integer> parse = (Map) JSON.parse(data);
            return parse;
        }
        return null;
    }

    @Override
    public boolean checkLePowerUpper(Double value, String device_id) {
        Map<String, String> deviceDetail = deviceManager.findOneDeviceDetail(device_id);

        if (deviceDetail == null || !deviceDetail.containsKey("forecast_power_upper_limit") || value == null ){
            return false;
        }
        Double forecastPowerUpperLimit = Double.valueOf(deviceDetail.get("forecast_power_upper_limit"));
        return value <= forecastPowerUpperLimit;
    }

}
